package mond_mons;

#########################################################################
# Perl Object Module to handle loading/checking the available monitors	#
# for the event monitor daemon. 

use XML::Parser;
use Carp qw(cluck);
use strict;

my $error_str=undef;
my $logmsg_hdlr=undef;
my $warnmsg_hdlr=undef;

sub error {
	return $error_str;
}

sub set_logmsg_hdlr {
	$logmsg_hdlr=$_[0];
}

sub set_warnmsg_hdlr {
	$warnmsg_hdlr=$_[0];
}

sub msg {
	if($_[0] eq "log" && defined($logmsg_hdlr)) {
		&{$logmsg_hdlr}($_[1]);
	}
	if($_[0] eq "warn" && defined($warnmsg_hdlr)) {
		&{$warnmsg_hdlr}($_[1]);
	}
}

#########################################################################
# Class methods:							#
# ==============							#
# error - return latest error string or undef if everything was OK.	#
# set_logmsg_hdlr -  the routine to call to log a message - no logging	#
# 		     occurs if not set.					#
# set_warnmsg_hdlr - Issue a warning message via this routine - if	#
#		     available.						#
#########################################################################

#########################################################################
# 									#
# The new method does not expect any arguments since the contents to	#
# parse are expected to be passed as a string using the parse method.	#
#									#
#########################################################################

sub new {
my $self;
	#################################################################
	# Now load in the XML using the XML::Parser - not XML simple.	#
	#################################################################
	
	$self={};
	$self->{dir}="$::ENV{TRUECL_CODE}/monitors";

	$self->{valid_node_monitors}=undef;
	$self->{valid_app_monitors}=undef;
	bless($self);
	return $self;
}

sub reconfigure {
my $self=shift;

	$self->{valid_node_monitors}=undef;
	$self->{valid_app_monitors}=undef
}

sub _get_valid_node_monitors {
my $self=shift;
my @OK=();
my @BAD=();

	$error_str=undef;
	my $dfd;
	if(!opendir($dfd,"$self->{dir}/node")) {
		$error_str="Unable to open directory $self->{dir}/node: $!";
		return 0;
	}
	my $x;
	while($x=readdir($dfd)) {
		next if $x !~ /\.pm$/;
		next if ! -f "$self->{dir}/node/$x";
		$x =~ s/\.pm$//;
		my $r=eval "use node::$x;";
		if(defined($@) && length($@)) {
			push @BAD,$x;
			msg("warn","Compile error for $x: $@");
			next;
		} else {
			msg("log","Node Monitor '$x' successfully loaded.");
		}
		push @OK,$x;
	}
	closedir($dfd);
	$self->{valid_node_monitors}=[@OK];
	return 1;
}

sub _get_valid_app_monitors {
my $self=shift;
my @OK=();
my @BAD=();

	$error_str=undef;
	my $dfd;
	if(!opendir($dfd,"$self->{dir}/app")) {
		$error_str="Unable to open directory $self->{dir}/app: $!";
		return 0;
	}
	my $x;
	while($x=readdir($dfd)) {
		next if $x !~ /\.pm$/;
		next if ! -f "$self->{dir}/app/$x";
		$x =~ s/\.pm$//;
		my $r=eval "use app::$x;";
		if(defined($@) && length($@)) {
			push @BAD,$x;
			msg("warn","Compile error for $x: $@");
			next;
		} else {
			msg("log","Application Monitor '$x' successfully loaded.");
		}
		push @OK,$x;
	}
	closedir($dfd);
	$self->{valid_app_monitors}=[@OK];
	return 1;
}

sub get_valid_app_monitors {
my $self=shift;

	if(!defined($self->{valid_app_monitors})) {
		my $r=_get_valid_app_monitors($self);
		return(undef) if!$r;
	}
	return [@{$self->{valid_app_monitors}}];
}

sub get_valid_node_monitors {
my $self=shift;

	if(!defined($self->{valid_node_monitors})) {
		my $r=_get_valid_node_monitors($self);
		return(undef) if!$r;
	}
	return [@{$self->{valid_node_monitors}}];
	
}

1;
